package homework_2;

import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;

import javax.imageio.ImageIO;

abstract class ImageFliter {
	/*
	 * This abstract mathod is uesd to zoom in or zoom out a picture in each subclass.
	 * When 0 < widthScale, heightScale < 1 , the picture will be zoomed in.
	 * When 1 < widthScale, heightScale, the picture will be zoomed out.
	 */
	abstract public BufferedImage imageScale(String pathName, float widthScale, float heightScale) throws IOException;
	/*
	 * This mothed is used to cut a picture.
	 * 0 < xStartScale < xEndScale <= 1
	 * 0 < yStartScale < yEndScale <= 1
	 */
	public BufferedImage cutImage(String pathName, float xStartScale, float yStartScale, float xEndScale, float yEndScale) throws IOException {
		if (!pathName.endsWith("png") && !pathName.endsWith("jpg") && !pathName.endsWith("bmp")) {
			throw new RuntimeException("Wrrong File!");
		}
		if (xStartScale > xEndScale || yStartScale > yEndScale ||
				xStartScale < 0 || yStartScale < 0 ||
				xEndScale > 1.0 || yEndScale > 1.0) {
			throw new RuntimeException("Wrrong Parameter!");
		}
		File file = new File(pathName);
		BufferedImage bufferedImage = ImageIO.read(file);
		
		int width = bufferedImage.getWidth();
		int height = bufferedImage.getHeight();
		int xStart = (int)(width * xStartScale);
		int yStart = (int)(height * yStartScale);
		int xEnd = (int)(width * xEndScale);
		int yEnd = (int)(height * yEndScale);
		
		int destW = xEnd - xStart;
		int destH = yEnd - yStart;
		
		int[] inPixels = bufferedImage.getRGB(0, 0, width, height, null, 0, width);
		int[] outPixels = new int[destH * destW];
		for (int y = 0; y < destH; y++) {
			int ys = y + yStart;
			for (int x = 0; x < destW; x++) {
				outPixels[y * destW + x] = inPixels[ys * width + x + xStart];
			}
		}
		BufferedImage bufImg = new BufferedImage(destW, destH,
				pathName.endsWith("png") ? BufferedImage.TYPE_INT_ARGB : BufferedImage.TYPE_INT_RGB);
		for (int i = 0; i < destH; i++) {
			for (int j = 0; j < destW; j++) {
				bufImg.setRGB(j, i, outPixels[i * destW + j]);
			}
		}
		return bufImg;
	}
}
